/*
 *@(#)SupportController.java 1.0 Feb 1, 2008
 *Copyright Fution Bai
 *
 */
package codebush.web.controller;

import java.io.IOException;
import java.util.HashMap;
import java.util.Map;

import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.servlet.ModelAndView;

import codebush.domain.Users;
import codebush.service.Support;
import codebush.util.HttpUtil;
import codebush.web.WebHelp;

/**
 * 
 * @author Fution Bai
 * @since 1.0
 */
@Controller
public class SupportController {

	private final Support support;

	@Autowired
	public SupportController(Support support) {
		this.support = support;
	}

	public Support getSupport() {
		return support;
	}

	@RequestMapping("/signup")
	public String signup(@RequestParam(value = "name")
	String name, @RequestParam(value = "password")
	String password, @RequestParam(value = "email")
	String email, HttpSession session, HttpServletResponse response) {
		Map map = this.getSupport().signup(name, password, email);
		if ((Boolean) map.get("result")) {
			signin(email, password, null, null, session, response);
			return "redirect:/";
		}
		return "/support/signup";
	}

	@RequestMapping("/signin")
	public ModelAndView signin(@RequestParam(value = "email", required = false)
	String email, @RequestParam(value = "password", required = false)
	String password, @RequestParam(value = "remember", required = false)
	String remember, @RequestParam(value = "redir", required = false)
	String redirectUrl, HttpSession session, HttpServletResponse response) {
		ModelAndView mav = new ModelAndView();
		if (email == null || email.equals("")) {
			mav.addObject("warnMessage", "Email is required.");
			mav.setViewName("/support/signin");
			return mav;
		}
		if (password == null || password.equals("")) {
			mav.addObject("warnMessage", "Password is required.");
			mav.setViewName("/support/signin");
			return mav;
		}
		Map<String, Object> map = this.getSupport().signin(email, password);
		if (map.get("registered") != null && (Boolean) map.get("registered") == false) {
			mav.addObject("warnMessage", "The email is not registered.");
			mav.setViewName("/support/signin");
			return mav;
		}
		if (map.get("result") != null && (Boolean) map.get("result")) {
			session.setAttribute("email", email);
			session.setAttribute("userName", ((Users) map.get("users")).getName());
			session.setAttribute("userId", ((Users) map.get("users")).getId());
			boolean isRemember = false; // whether the user select"在这台电脑上记住我"
			if (remember != null && remember.equals("on")) {
				isRemember = true;
			}
			if (isRemember == true) {
				response.addCookie(HttpUtil.generateRememberMeCookie("userId", ((Users) map.get("users")).getId()));
				response.addCookie(HttpUtil.generateRememberMeCookie("userName", ((Users) map.get("users")).getName()));
				response.addCookie(HttpUtil.generateRememberMeCookie("email", ((Users) map.get("users")).getEmail()));
			}
			if (redirectUrl != null && !redirectUrl.equals("")) {
				mav.setViewName("redirect:" + redirectUrl);
				return mav;
			}
			mav.setViewName("redirect:/home/?");
			return mav;
		} else {
			mav.addObject("warnMessage", "Password does not match email:<I><strong>" + email + "</strong></I>");
			mav.setViewName("/support/signin");
			return mav;
		}
	}

	/**
	 * direct the user to the url
	 * 
	 * @param url
	 * @return
	 */
	@RequestMapping("/")
	public String go(@RequestParam(value = "url")
	String url) {
		return url;
	}

	@RequestMapping("/mail/retrieve")
	public String mailRetrieve() {
		this.getSupport().mailRetrieve();
		return "/support/redirect/global_success";
	}

	/**
	 * for the user to reset the password, if he/she forgot the password.
	 * 
	 * @param email
	 * @param i
	 * @param password
	 * @return
	 */
	@RequestMapping("/password/reset")
	public ModelAndView passwordReset(@RequestParam(value = "email", required = false)
	String email, @RequestParam(value = "i", required = false)
	String i, @RequestParam(value = "password", required = false)
	String password) {
		String md5text = i;
		ModelAndView mav = new ModelAndView();
		mav.setViewName("/support/password_reset");
		Map<String, String> model = new HashMap<String, String>();
		if (email == null && md5text == null && password == null) {
			return mav;
		}
		if (email != null && md5text == null && password == null) {
			String result1 = this.getSupport().passwordReset(email, null, null);
			if (result1.equals("email_not_registered")) {
				model.put("message", "The email has not been registered on this site!");
				mav.addAllObjects(model);
				return mav;
			}
			if (result1.equals("email_for_reset_password_sent")) {
				md5text = result1;
				model.put("message", "Please check your mail " + email + " to reset your password!");
				mav.addAllObjects(model);
				return mav;
			}
		}
		if (md5text != null && md5text.length() == 32 && password == null) {
			String result = this.getSupport().passwordReset(null, md5text, null);
			if (result.equals("confirmed")) {
				model.put("confirmed", "confirmed");
				mav.addAllObjects(model);
			}
		}
		if (md5text != null && md5text.length() == 32 && password != null && email != null) {
			String result = this.getSupport().passwordReset(email, md5text, password);
			if (result.equals("success")) {
				mav.setViewName("/support/signin");
			}
		}
		return mav;
	}

	/**
	 * for the user to logout
	 * 
	 * @param session
	 * @param request
	 * @param response
	 * @throws IOException
	 */
	@RequestMapping("/logout")
	public void logout(HttpSession session, HttpServletRequest request, HttpServletResponse response) throws IOException {
		WebHelp.invalidateUser(session, request, response);
		response.sendRedirect("/codebush/");
	}

	/**
	 * for users to feedback about the site
	 * 
	 * @return
	 */
	@RequestMapping("/appreciated")
	public ModelAndView feedback(@RequestParam(value = "title", required = false)
	String title, @RequestParam(value = "discription", required = false)
	String discription, @RequestParam(value = "email", required = false)
	String email, HttpSession session) {
		ModelAndView mav = new ModelAndView();
		if (title == null || title.equals("")) {
			mav.setViewName("support/feedback");
			return mav;
		}
		if (email == null || email.equals("")) {
			email = HttpUtil.getEmail(session);
		}
		this.getSupport().insertFeedback(title, discription, email);
		mav.setViewName("redirect:/?");
		return mav;
	}

	/**
	 * used to verify the user's password for deciding the user's identification
	 * 
	 * @param session
	 * @param _continue
	 * @param password
	 * @param response
	 * @return
	 * @throws IOException
	 */
	@RequestMapping("/verifyPassword")
	public ModelAndView verifyPassword(HttpSession session, @RequestParam(value = "_continue", required = false)
	String _continue, @RequestParam(value = "password", required = false)
	String password, HttpServletResponse response) throws IOException {
		ModelAndView mav = new ModelAndView();
		if (session.getAttribute("passwordVerified") == null) {
			String email = (String) session.getAttribute("email");
			Map<String, Object> map = this.getSupport().signin(email, password);
			if (map.get("result") != null && (Boolean) map.get("result")) {
				session.setAttribute("passwordVerified", true);
				response.sendRedirect(_continue);
				return null;
			}
		}
		mav.setViewName("/support/verify_password");
		mav.addObject("_continue", _continue);
		return mav;
	}

	/**
	 * if the user want to alter his/her password, goes here
	 * 
	 * @return
	 * @throws IOException
	 */
	@RequestMapping("/password/alter")
	public ModelAndView alterPassord(@RequestParam(value = "newPassword", required = false)
	String newPassword, HttpSession session, HttpServletRequest request, HttpServletResponse response) throws IOException {
		if (session.getAttribute("passwordVerified") == null) {
			WebHelp.sendRedirectToVerifyPassword(session, request, response);
			return null;
		}
		ModelAndView mav = new ModelAndView();
		if(newPassword == null && (Boolean)session.getAttribute("passwordVerified")){
			mav.setViewName("support/password_alter");
			return mav;
		}
		if(newPassword != null && (Boolean)session.getAttribute("passwordVerified")){
			String email = session.getAttribute("email").toString();
			this.getSupport().alterPassword(newPassword, email);
			session.removeAttribute("passwordVerified");
			mav.setViewName("support/redirect/global_success");
			return mav;
		}
		return null;
	}
}
